<template>
  <Modal
    v-model:visible="visible"
    primary-cancel
    ref="modalRef"
    :title="title"
    :ok-text="dismissText || $t('APP.Common.Confirm.Text')"
    :cancel-text="cancelText"
    @ok="emit('confirm')"
    @cancel="emit('cancel')"
  >
    <view class="hint-container">
      <view v-for="(step, index) in stepList" :key="index" class="step-row">
        <scroll-view class="hint-content" scroll-y :style="{ height: imgHeight }">
          <image class="step-image" mode="widthFix" :src="getStepImage(step)" @load="calculateMaxHeight" />
        </scroll-view>
        <rich-text :nodes="step.html_code" />
      </view>
    </view>
  </Modal>
</template>

<script setup lang="ts">
import { getRemoteControlGuide } from '@/api/appliance'
import type { ChapterItem } from '@/api/content'
import Modal from '@/common/modal.vue'
import netconfig from '@/config/netconfig'

export type StepsGetter = (steps: ChapterItem[]) => ChapterItem[]

const props = defineProps<{
  show: boolean
  vib: string
  title: string
  dismissText: string
  cancelText?: string
  stepsGetter?: StepsGetter
}>()
const emit = defineEmits<{
  (e: 'update:show', show: boolean): void
  (e: 'confirm'): void
  (e: 'cancel'): void
}>()

const visible = computed({
  get() {
    return props.show && Array.isArray(stepList.value)
  },
  set(show) {
    emit('update:show', show)
  },
})

watch(
  () => props.show,
  (show) => {
    show && loadData()
  }
)

const stepList = ref<ChapterItem[] | null>(null)
async function loadData() {
  const res = await getRemoteControlGuide(props.vib)
  let steps = res.data.step_list
  if (typeof props.stepsGetter === 'function') {
    try {
      steps = props.stepsGetter(steps)
    } catch (e) {
      console.error(e)
    }
  }

  stepList.value = steps
}
const modalRef = ref<InstanceType<typeof Modal> | null>(null)
const imgHeight = ref('')
async function calculateMaxHeight() {
  if (!Array.isArray(stepList.value) || stepList.value.length === 0) return

  const [modalRect, hintRect] = await Promise.all([getRect('.modal-body', modalRef.value), getRect('.hint-container')])

  const modalHeight = modalRect.height || 0
  const modalTop = modalRect.top || 0
  const hintHeight = hintRect.height || 0
  const hintTop = hintRect.top || 0
  const padding = (hintTop - modalTop) * 2
  if (hintHeight > modalHeight) {
    imgHeight.value = `${modalHeight - padding}px`
  }
}

const instance = getCurrentInstance()
function getRect(selector: string, ref?: InstanceType<any>): Promise<UniApp.NodeInfo> {
  return new Promise((resolve, reject) => {
    try {
      uni
        .createSelectorQuery()
        .in(ref || instance)
        .select(selector)
        .boundingClientRect((rect) => {
          if (!rect) {
            return reject(`getBoundingClientRect failed by selector: ${selector}`)
          }
          return resolve(rect as UniApp.NodeInfo)
        })
        .exec()
    } catch (e) {
      console.error(e)
      reject(e)
    }
  })
}

function getStepImage(step: ChapterItem) {
  return netconfig.ASSETSPRE + step.pic_url
}
</script>

<style scoped lang="less">
.step-row {
  text-align: left;
}
.step-image {
  width: 100%;
}
:deep(.iconHeight) {
  margin: 0 8rpx;
  height: 56rpx;
  vertical-align: middle;
}
</style>
